package com.km.team.phsystem.web.controller;

import com.km.team.phsystem.beans.pojo.QueueInfo;
import com.km.team.phsystem.beans.vo.DispatchQueueVo;
import com.km.team.phsystem.beans.vo.QueueInfoCombinationVo;
import com.km.team.phsystem.beans.vo.QueueListAndStartTimeToStringVo;
import com.km.team.phsystem.beans.vo.ResponseData;
import com.km.team.phsystem.common.constants.Constants;
import com.km.team.phsystem.common.enums.QueueStatusEnum;
import com.km.team.phsystem.common.enums.ResultEnum;
import com.km.team.phsystem.web.controller.base.BaseController;
import com.km.team.phsystem.web.utils.ResponseDataUtil;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.*;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

/**
 * Author: jiangjun
 * Date: 2018-11-30
 * Time: 17:13
 * Description: 业务办理
 */
@RestController
@RequestMapping("/busi/process")
public class BusinessProcessController extends BaseController<BusinessProcessController> {

    /**
     * 获取排号信息
     * @param queueId
     * @return
     */
    private QueueInfo getQueueById(Integer queueId){
        //todo:应该是一样的。需要确认前端取值，不要出错
        return queueService.getDataForKey(queueId);
    }

    /**
     * 更新排号状态
     * @param queueInfo
     * @param windowId
     * @param status
     * @return
     */
    private int updateQueueInfo(QueueInfo queueInfo, String windowId, String status){
        queueInfo.setQueueStatus(status);
        queueInfo.setWindowId(windowId);
        queueInfo.setUpdateTime(new Date());
        return queueService.updateQueueStatusForKey(queueInfo);
    }

    /**
     * 排号跳过
     * @param queueId:排号
     * @param windowId：窗口号
     * @return
     * @throws Exception
     */
    @GetMapping("/skip/{queueId}/{windowId}")
    public ResponseData skip(@PathVariable("queueId") Integer queueId,
                             @PathVariable("windowId") String windowId) throws Exception{
        QueueInfo queueInfo = getQueueById(queueId);
        if(queueInfo == null){
            return ResponseDataUtil.buildError(Constants.ERROR, "没有获取到指定排号信息！");
        }
        updateQueueInfo(queueInfo, windowId, QueueStatusEnum.QUEUE_STATUS_SKIP.getType());
        return ResponseDataUtil.buildSuccess();
    }

    /**
     * 处理完成
     * @param queueId
     * @param windowId
     * @return
     * @throws Exception
     */
    @GetMapping("/complete/{queueId}/{windowId}")
    public ResponseData complete(@PathVariable("queueId") Integer queueId,
                             @PathVariable("windowId") String windowId) throws Exception{
        QueueInfo queueInfo = getQueueById(queueId);
        if(queueInfo == null){
            return ResponseDataUtil.buildError(Constants.ERROR, "没有获取到指定排号信息！");
        }
        updateQueueInfo(queueInfo, windowId, QueueStatusEnum.QUEUE_STATUS_PROCESS_COMPLETE.getType());
        return ResponseDataUtil.buildSuccess();
    }

    /**
     * 开始处理排号
     * @param queueId
     * @param windowId
     * @return
     * @throws Exception
     */
    @GetMapping("/start/{queueId}/{windowId}")
    public ResponseData start(@PathVariable("queueId") Integer queueId,
                                 @PathVariable("windowId") String windowId) throws Exception{
        QueueInfo queueInfo = getQueueById(queueId);
        if(queueInfo == null){
            return ResponseDataUtil.buildError(Constants.ERROR, "没有获取到指定排号信息！");
        }
        updateQueueInfo(queueInfo, windowId, QueueStatusEnum.QUEUE_STATUS_PROCESS_START.getType());
        return ResponseDataUtil.buildSuccess();
    }

    /**
     * 给窗口分配一个号为已分配-手动点击
     * @param dispatchId:分配排号id
     * @param unDispatchId：重置排号id
     * @param windowId
     * @return
     * @throws Exception
     */
    @GetMapping("/manual/dispatch/{dispatchId}/{unDispatchId}/{windowId}")
    public ResponseData manualDispatch(@PathVariable("dispatchId") Integer dispatchId,
                                       @PathVariable("unDispatchId") Integer unDispatchId,
                             @PathVariable("windowId") String windowId) throws Exception{
        QueueInfo unDispatchQueue = getQueueById(unDispatchId);
        QueueInfo dispatchQueue = null;
        // 没有已分配时，则为-1
        if(!dispatchId.equals(-1)){
            dispatchQueue = getQueueById(dispatchId);
        }

        if(unDispatchQueue == null && dispatchQueue == null){
            return ResponseDataUtil.buildError(Constants.ERROR, "没有获取到指定排号信息！");
        }
        // 先校验解绑排号状态
        if(unDispatchQueue != null &&
            QueueStatusEnum.startProcessList().contains(unDispatchQueue.getQueueStatus())) {
            return ResponseDataUtil.buildError(Constants.ERROR,
                unDispatchQueue.getQueueCode() + "排号不允许解绑窗口操作！状态："
                    + QueueStatusEnum.getNameByType(unDispatchQueue.getQueueStatus()));
        }
        // 校验绑定排号状态
        if(dispatchQueue != null &&
            QueueStatusEnum.startProcessList().contains(dispatchQueue.getQueueStatus())) {
            return ResponseDataUtil.buildError(Constants.ERROR,
                dispatchQueue.getQueueCode() + "排号不允许绑定窗口操作！状态：" +
                QueueStatusEnum.getNameByType(dispatchQueue.getQueueStatus()));
        }

        // 更新状态
        updateQueueInfo(unDispatchQueue, "", QueueStatusEnum.QUEUE_STATUS_DISPATCHED.getType());
        if(dispatchQueue != null) {
            updateQueueInfo(dispatchQueue, windowId, QueueStatusEnum.QUEUE_STATUS_MSG_SENDED.getType());
        }
        // 更新返回数据
        unDispatchQueue.setQueueStatus(QueueStatusEnum.QUEUE_STATUS_DISPATCHED.getType());
        unDispatchQueue.setWindowId(windowId);
        return ResponseDataUtil.buildSuccess(unDispatchQueue);
    }

    /**
     * 给窗口分配一个号为已分配-系统自动分配
     * @param vo
     * @return
     * @throws Exception
     */
    @PostMapping("/auto/dispatch")
    public ResponseData autoDispatch(@RequestBody DispatchQueueVo vo) throws Exception{
        if(vo.getDateTime() == null){
            return ResponseDataUtil.buildError(ResultEnum.PARAM_ERROR);
        }
        QueueListAndStartTimeToStringVo queueList = queueService.getNowTimeQueueList(vo.getBusiIdList(),vo.getWindowId(),vo.getDateTime());
        List<QueueInfoCombinationVo> list = queueList.getQueueInfoList();
        if(CollectionUtils.isEmpty(list)){
            return ResponseDataUtil.buildSuccess();
        }
        // 过滤是否有该排号未处理完成的排号，有则优先处理
        List<QueueInfoCombinationVo> dispatchedList = list.stream().filter(queue ->
            (queue.getQueueInfo().getWindowId() != null
                && queue.getQueueInfo().getWindowId().equals(vo.getWindowId()))
        ).collect(Collectors.toList());
        if(!CollectionUtils.isEmpty(dispatchedList)){
            ResponseDataUtil.buildSuccess(dispatchedList.get(0));
        }
        QueueInfoCombinationVo queue = list.get(0);
        queue.getQueueInfo().setQueueStatus(QueueStatusEnum.QUEUE_STATUS_DISPATCHED.getType());
        updateQueueInfo(queue.getQueueInfo(), vo.getWindowId(),
            QueueStatusEnum.QUEUE_STATUS_DISPATCHED.getType());

        return ResponseDataUtil.buildSuccess(queue);
    }
}
